(*
   Copyright (C) 2024 International Digital Economy Academy.
   This program is licensed under the MoonBit Public Source
   License as published by the International Digital Economy Academy,
   either version 1 of the License, or (at your option) any later
   version. This program is distributed in the hope that it will be
   useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the MoonBit
   Public Source License for more details. You should have received a
   copy of the MoonBit Public Source License along with this program. If
   not, see
   <https://www.moonbitlang.com/licenses/moonbit-public-source-license-v1>.
*)


module Menhir_token = Lex_menhir_token

let token_kind_to_expect_string (t : Menhir_token.token_kind) =
  match t with
  | Token_kind T_error -> assert false
  | Token_kind T_WHILE -> "`while`"
  | Token_kind T_UNDERSCORE -> "`_`"
  | Token_kind T_UIDENT -> "identifier"
  | Token_kind T_TYPE -> "`type`"
  | Token_kind T_TYPEALIAS -> "`typealias`"
  | Token_kind T_TRUE -> "`true`"
  | Token_kind T_STRUCT -> "`struct`"
  | Token_kind T_STRING -> "string"
  | Token_kind T_MULTILINE_STRING -> "multiline string"
  | Token_kind T_MULTILINE_INTERP -> "multiline string interpolation"
  | Token_kind T_SEMI -> "`;`"
  | Token_kind T_RPAREN -> "`)`"
  | Token_kind T_RETURN -> "`return`"
  | Token_kind T_THROW -> "`throw`"
  | Token_kind T_RAISE -> "`raise`"
  | Token_kind T_TRY -> "`try`"
  | Token_kind T_CATCH -> "`catch`"
  | Token_kind T_READONLY -> "`readonly`"
  | Token_kind T_RBRACKET -> "`]`"
  | Token_kind T_RBRACE -> "`}`"
  | Token_kind T_PUB -> "`pub`"
  | Token_kind T_PRIV -> "`priv`"
  | Token_kind T_PLUS -> "+"
  | Token_kind T_PACKAGE_NAME -> "package name"
  | Token_kind T_NEWLINE -> "new line"
  | Token_kind T_MUTABLE -> "`mut`"
  | Token_kind T_MINUS -> "`-`"
  | Token_kind T_MATCH -> "`match`"
  | Token_kind T_LPAREN -> "`(`"
  | Token_kind T_LIDENT -> "`identifier`"
  | Token_kind T_POST_LABEL -> "`label~`"
  | Token_kind T_LET -> "`let`"
  | Token_kind T_LBRACKET -> "`[`"
  | Token_kind T_LBRACE -> "`{`"
  | Token_kind T_IMPL -> "`impl`"
  | Token_kind T_WITH -> "`with`"
  | Token_kind T_INT -> "integer"
  | Token_kind T_BYTE -> "byte"
  | Token_kind T_BYTES -> "bytes"
  | Token_kind T_INFIX4 -> "infix 4"
  | Token_kind T_INFIX3 -> "infix 3"
  | Token_kind T_INFIX2 -> "infix 2"
  | Token_kind T_INFIX1 -> "infix 1"
  | Token_kind T_QUESTION -> "`?`"
  | Token_kind T_EXCLAMATION -> "`!`"
  | Token_kind T_TRAITALIAS -> "`traitalias`"
  | Token_kind T_TRAIT -> "`trait`"
  | Token_kind T_DERIVE -> "derive"
  | Token_kind T_IMPORT -> "`import`"
  | Token_kind T_EXTERN -> "`extern`"
  | Token_kind T_IF -> "`if`"
  | Token_kind T_FN -> "`fn`"
  | Token_kind T_FLOAT -> "float"
  | Token_kind T_FAT_ARROW -> "`=>`"
  | Token_kind T_THIN_ARROW -> "`->`"
  | Token_kind T_FALSE -> "`false`"
  | Token_kind T_EQUAL -> "`=`"
  | Token_kind T_AUGMENTED_ASSIGNMENT -> "`augmented assignment`"
  | Token_kind T_EOF -> "`end of file`"
  | Token_kind T_ENUM -> "`enum`"
  | Token_kind T_ELSE -> "`else`"
  | Token_kind T_DOT_UIDENT -> "`.` identifier"
  | Token_kind T_DOT_LIDENT -> "`.` identifier"
  | Token_kind T_DOT_INT -> "`.` integer"
  | Token_kind T_CONTINUE -> "`continue`"
  | Token_kind T_CONST -> "`const`"
  | Token_kind T_COMMENT -> "comment"
  | Token_kind T_COMMA -> "`,`"
  | Token_kind T_COLONCOLON -> "`::`"
  | Token_kind T_COLON -> "`:`"
  | Token_kind T_CHAR -> "character"
  | Token_kind T_BREAK -> "`break`"
  | Token_kind T_BARBAR -> "`||`"
  | Token_kind T_BAR -> "`|`"
  | Token_kind T_ASYNC -> "`async`"
  | Token_kind T_AS -> "`as`"
  | Token_kind T_AMPERAMPER -> "`&&`"
  | Token_kind T_DOTDOT -> ".."
  | Token_kind T_RANGE_INCLUSIVE -> "..="
  | Token_kind T_RANGE_EXCLUSIVE -> "..<"
  | Token_kind T_INTERP -> "string interpolation"
  | Token_kind T_TEST -> "`test`"
  | Token_kind T_LOOP -> "`loop`"
  | Token_kind T_FOR -> "`for`"
  | Token_kind T_IN -> "`in`"
  | Token_kind T_PIPE -> "|>"
  | Token_kind T_AMPER -> "`&`"
  | Token_kind T_CARET -> "`^`"
  | Token_kind T_GUARD -> "guard"
  | Token_kind T_ELLIPSIS -> "`...`"
  | Token_kind T_ATTRIBUTE -> "`attribute`"
  | Token_kind T_IS -> "`is`"
  (* 中文关键字 *)
  | Token_kind Menhir_token.T_FN_CH -> "`法`"
  | Token_kind Menhir_token.T_LET_CH -> "`令`"
  | Token_kind Menhir_token.T_VAR_CH -> "`变量`"
  | Token_kind Menhir_token.T_IF_CH -> "`若`"
  | Token_kind Menhir_token.T_ELSE_CH -> "`否则`"
  | Token_kind Menhir_token.T_FOR_CH -> "`环`"
  | Token_kind Menhir_token.T_WHILE_CH -> "`当`"
  | Token_kind Menhir_token.T_RETURN_CH -> "`返`"
  | Token_kind Menhir_token.T_STRUCT_CH -> "`结构`"
  | Token_kind Menhir_token.T_ENUM_CH -> "`举`"
  | Token_kind Menhir_token.T_MATCH_CH -> "`匹配`"
  | Token_kind Menhir_token.T_PUB_CH -> "`公`"
  | Token_kind Menhir_token.T_IN_CH -> "`在`"
  | Token_kind Menhir_token.T_SOME_CH -> "`一些`"
  | Token_kind Menhir_token.T_NONE_CH -> "`无`"
  | Token_kind Menhir_token.T_END_CH -> "`完`"

let token_to_string = function
  | Menhir_token.CHAR { char_repr; _ } -> "'" ^ char_repr ^ "'"
  | INT s -> s
  | BYTE { byte_repr; _ } -> "b'" ^ byte_repr ^ "'"
  | BYTES { bytes_repr; _ } -> "b\"" ^ bytes_repr ^ "\""
  | FLOAT s -> s
  | STRING { string_repr; _ } -> "\"" ^ string_repr ^ "\""
  | MULTILINE_STRING s -> "#|" ^ s
  | MULTILINE_INTERP interp ->
      "$|" ^ Lex_literal.interp_content_to_string interp
  | INTERP interp -> Lex_literal.interp_literal_to_string interp
  | LIDENT s | UIDENT s -> s
  | POST_LABEL s -> s ^ "~"
  | COMMENT { content; _ } -> content
  | NEWLINE -> "\n"
  | INFIX1 s | INFIX2 s | INFIX3 s | INFIX4 s -> s
  | AUGMENTED_ASSIGNMENT s -> s ^ "="
  | EOF -> ""
  | FALSE -> "false"
  | TRUE -> "true"
  | PUB -> "pub"
  | PRIV -> "priv"
  | READONLY -> "readonly"
  | IMPORT -> "import"
  | EXTERN -> "extern"
  | BREAK -> "break"
  | CONTINUE -> "continue"
  | CONST -> "const"
  | STRUCT -> "struct"
  | ENUM -> "enum"
  | TRAITALIAS -> "traitalias"
  | TRAIT -> "trait"
  | DERIVE -> "derive"
  | IMPL -> "impl"
  | WITH -> "with"
  | RAISE -> "raise"
  | THROW -> "throw"
  | TRY -> "try"
  | CATCH -> "catch"
  | EQUAL -> "="
  | LPAREN -> "("
  | RPAREN -> ")"
  | COMMA -> ","
  | MINUS -> "-"
  | QUESTION -> "?"
  | EXCLAMATION -> "!"
  | DOT_UIDENT s -> "." ^ s
  | DOT_LIDENT s -> "." ^ s
  | DOT_INT s -> "." ^ Int.to_string s
  | COLONCOLON -> "::"
  | COLON -> ":"
  | SEMI true -> ";"
  | SEMI false -> ""
  | LBRACKET -> "["
  | PLUS -> "+"
  | RBRACKET -> "]"
  | UNDERSCORE -> "_"
  | BAR -> "|"
  | LBRACE -> "{"
  | RBRACE -> "}"
  | AMPERAMPER -> "&&"
  | BARBAR -> "||"
  | ASYNC -> "async"
  | AS -> "as"
  | PIPE -> "|>"
  | ELSE -> "else"
  | FN -> "fn"
  | IF -> "if"
  | LET -> "let"
  | MATCH -> "match"
  | MUTABLE -> "mut"
  | TYPE -> "type"
  | TYPEALIAS -> "typealias"
  | FAT_ARROW -> "=>"
  | THIN_ARROW -> "->"
  | WHILE -> "while"
  | RETURN -> "return"
  | DOTDOT -> ".."
  | RANGE_INCLUSIVE -> "..="
  | RANGE_EXCLUSIVE -> "..<"
  | TEST -> "test"
  | LOOP -> "loop"
  | FOR -> "for"
  | IN -> "in"
  | PACKAGE_NAME s -> "@" ^ s
  | AMPER -> "&"
  | CARET -> "^"
  | GUARD -> "guard"
  | ELLIPSIS -> "..."
  | ATTRIBUTE s -> "#" ^ s
  | IS -> "is"
  (* 中文关键字 *)
  | FN_CH _ -> "法"
  | LET_CH _ -> "令"
  | VAR_CH _ -> "变量"
  | IF_CH _ -> "若"
  | ELSE_CH _ -> "否则"
  | FOR_CH _ -> "环"
  | WHILE_CH _ -> "当"
  | RETURN_CH _ -> "返"
  | STRUCT_CH _ -> "结构"
  | ENUM_CH _ -> "举"
  | MATCH_CH _ -> "匹配"
  | PUB_CH _ -> "公"
  | IN_CH _ -> "在"
  | SOME_CH _ -> "一些"
  | NONE_CH _ -> "无"
  | END_CH _ -> "完"
